import type { ConfigEnv, UserConfig } from 'vite'

import { fileURLToPath, URL } from 'node:url'

import dayjs from 'dayjs'

import { loadEnv } from 'vite'

import pkg from './package.json'

import { createVitePlugins } from './vite/plugins'

import { wrapperEnv } from './vite/utils'

const { dependencies, devDependencies, name, version } = pkg

const __APP__: AppInfo = {
  pkg: { dependencies, devDependencies, name, version },
  lastBuildTime: dayjs(new Date()).format('YYYY-MM-DD HH:mm:ss')
}

// https://vitejs.dev/config/
export default ({ command, mode }: ConfigEnv): UserConfig => {
  const isBuild = command === 'build'
  const root = process.cwd()
  const env = loadEnv(mode, root)
  const viteEnv = wrapperEnv(env)

  return {
    define: {
      // 应用信息
      __AppInfo__: JSON.stringify(__APP__)
    },

    plugins: [createVitePlugins(viteEnv, isBuild)],

    css: {
      preprocessorOptions: {
        scss: {
          api: 'modern-compiler'
        }
      }
    },

    resolve: {
      alias: {
        '@': fileURLToPath(new URL('./src', import.meta.url))
      }
    },

    esbuild: {
      // 生产环境去除console、debugger
      drop: command === 'build' && mode === 'production' ? ['console', 'debugger'] : []
    },

    build: {
      chunkSizeWarningLimit: 3000,
      rollupOptions: {
        output: {
          // 最小化拆分包
          manualChunks(id) {
            if (id.includes('node_modules')) {
              return id
                .toString()
                .replace('/.pnpm', '')
                .split('node_modules/')[1]
                .split('/')[0]
                .replace(/@\d+.\d+.\d[\w+]*/g, '')
                .toString()
            }
          },

          // 用于从入口点创建的块的打包输出格式[name]表示文件名,[hash]表示该文件内容hash值
          entryFileNames: 'js/[name].[hash].js',

          // 用于命名代码拆分时创建的共享块的输出命名
          // 用于输出静态资源的命名，[ext]表示文件扩展名
          assetFileNames: '[ext]/[name].[hash].[ext]',

          // 拆分js到模块文件夹
          chunkFileNames: (chunkInfo) => {
            const facadeModuleId = chunkInfo.facadeModuleId
              ? chunkInfo.facadeModuleId.split('/')
              : []

            const fileName = facadeModuleId[facadeModuleId.length - 2] || '[name]'

            return `js/${fileName}/[name].[hash].js`
          }
        }
      }
    },

    preview: {
      port: 10200,
    },

    server: {
      hmr: { overlay: false },
      port: 10100,
      host: true,

      proxy: {
        '/gsapi': {
          target: 'https://v1.jinrishici.com',
          changeOrigin: true,
          rewrite: (path) => path.replace(/^\/gsapi/, ''),
          headers: {
            referer: 'http://hlfine.com/',
            origin: 'http://hlfine.com'
          }
        },
        '/hitokoto': {
          target: 'https://v1.hitokoto.cn',
          changeOrigin: true,
          rewrite: (path) => path.replace(/^\/hitokoto/, ''),
          headers: {
            referer: 'http://hlfine.com/',
            origin: 'http://hlfine.com'
          }
        },
        '/fonts': {
          target: 'http://cdn.hlfine.com/',
          changeOrigin: true,
          headers: {
            referer: 'http://hlfine.com/',
            origin: 'http://hlfine.com'
          }
        },
        '/local': {
          target: 'http://localhost:3000',
          changeOrigin: true,
          rewrite: (path) => path.replace(/^\/local/, '')
        }
      }
    }
  }
}
